/**
 * @FileName AsyncRequest.java
 * @Date 2012-3-20
 * @Author 李航杰
 */
package com.sharemob.tinchat.lib.common;

import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.io.UnsupportedEncodingException;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.HttpClient;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.params.HttpConnectionParams;
import org.apache.http.protocol.HTTP;
import org.json.JSONException;

import android.annotation.SuppressLint;
import android.os.AsyncTask;
import android.util.Base64;

/**
 * 只可用于JSON POST请求
 * 
 * @author 李航杰
 */
@SuppressLint("NewApi")
public final class AsyncHttpRequest extends AsyncTask<Void, Void, String> {

	 private static final int    timeoutConnection = 5 * 1000;
	 private static final int    timeoutSocket     = 5 * 1000;
	/** 是否被取消 */
	private volatile boolean isCanceled = false;
	/**加密**/
	private boolean encryption=false;
	/** 是否请求中 */
	private boolean isLoading = false;

	/** 是否已完成 */
	private boolean isFinished = false;

	/** 请求地址 */
	private String mUrl;

	/** 请求参数 */
	private Map<String,Object> parameterMap;
	private String parameterString;

	/** 回调接口 */
	private RequestCallback mCallback;

	private HttpClient httpclient;

	public boolean isLoading() {
		return isLoading;
	}

	public boolean isCanceled() {
		return isCanceled;
	}

	public AsyncHttpRequest() {
	}

	/**
	 * 执行异步网络请求
	 * 
	 * @param url
	 * @param param
	 * @param method
	 * @param callback
	 * @exception throws
	 */
	public void doRequest(String url,Map<String,Object> parameter,RequestCallback callback) {
		if (this.isCanceled || this.isFinished || this.isLoading) {
			throw new IllegalStateException();
		}
		httpclient = new DefaultHttpClient();
		this.mUrl = url;
		this.parameterMap=parameter;
		this.mCallback = callback;
		this.execute();
	}

	/**
	 * 执行异步网络请求
	 * 
	 * @param url
	 * @param param
	 * @param method
	 * @param callback
	 * @exception throws
	 */
	public void doRequest(String url,String parameter,boolean encryption,RequestCallback callback) {
		if (this.isCanceled || this.isFinished || this.isLoading) {
			throw new IllegalStateException();
		}
		httpclient = new DefaultHttpClient();
		this.mUrl = url;
		this.parameterString=parameter;
		this.encryption=encryption;
		this.mCallback = callback;
		this.execute();
	}
	private HttpEntity MapToHttpEntity(Map<String,Object> parameters){
		HttpEntity requestHttpEntity = null;

		try {
			List<NameValuePair> pairList = new ArrayList<NameValuePair>();
			Iterator<String> iter=parameters.keySet().iterator();
			if(iter.hasNext()){
				String key=iter.next();
				NameValuePair object = new BasicNameValuePair(key,(String)parameters.get(key));
				pairList.add(object);
			}
			 requestHttpEntity = new UrlEncodedFormEntity( pairList, HTTP.UTF_8);
		} catch (UnsupportedEncodingException e) {
			e.printStackTrace();
		}
		return requestHttpEntity;
	}
	
	/**
	 * 能够正确返回才算网络请求成功
	 * 
	 * @return
	 * @throws ClientProtocolException
	 * @throws IOException
	 * @throws JSONException
	 * @throws FileNotFoundException
	 * @exception throws
	 */
	private String request() {
		
		HttpPost httppost = new HttpPost(mUrl);
		System.out.println("---url:"+mUrl);
		// 添加http头信息
		httppost.addHeader("Content-Type", "application/json; charset=utf-8");  
		httppost.getParams().setIntParameter(HttpConnectionParams.SO_TIMEOUT,timeoutSocket); //超时设置
		httppost.getParams().setIntParameter(HttpConnectionParams.CONNECTION_TIMEOUT, timeoutConnection);//连接超时
		try {
			
			if(this.parameterMap!=null){
				httppost.setEntity(MapToHttpEntity(this.parameterMap));
			}else if(this.parameterString!=null){
				httppost.setEntity(new StringEntity(this.parameterString, "UTF-8"));
			}
			
			// http post的json数据格式： {"name": "your name","parentId":"id_of_parent"}
			HttpResponse response = null;
			String json=null;
			response = httpclient.execute(httppost);
			
			// 检验状态码，如果成功接收数据
			int code = response.getStatusLine().getStatusCode();
			if (code ==200) {
				HttpEntity httpEntity = response.getEntity();
				InputStream is = null;
				try
	            {
	                is = httpEntity.getContent();
	                if(is!=null){
	                	 if(encryption){
	                  		json=decode(getContent(is));
	                  	}else{
	                  		json=getContent(is);
	                  	}
	                }
	              
	                return json;
	            }
	            catch (Exception e)
	            {
	            	json=null;
//	                e.printStackTrace();
	            }
	            finally{
	                try
	                {
	                    if(is!=null){
	                        is.close();
	                    }
	                }
	                catch (IOException e)
	                {
	                }
	        }

				
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
		return null;
	}
    /**
     * 
     * <一句话功能简述>
     * <将InputStream流 转化未字符串>
     * @param is
     * @return [参数说明]
     */
    public  String getContent(InputStream is){
        String content=null;
        int length=1024*1024;
        byte[] byteBuffer=new byte[length];
        int size=-1;
        try {
            size = is.read(byteBuffer);
            content=new String(byteBuffer,0,size!=-1?size:0);
        } catch (IOException e) {
            e.printStackTrace();
        }
        return content;
    }
    /**
     * BASE64
     * @param base64Str
     * @return
     */
    private static String decode(String base64Str){
      byte[] buffer = Base64.decode(base64Str, Base64.DEFAULT);
      return new String(buffer);
  }
    
	@Override
	protected void onCancelled() {
		isCanceled = true;
		if (httpclient != null) {
			httpclient.getConnectionManager().shutdown();
		}
	}

	@Override
	protected void onPostExecute(String result) {
		isLoading = false;
		isFinished = true;
		if (!isCanceled && mCallback != null) {
			if (result != null) {
				mCallback.requestDidFinished(result);
			} else {
				mCallback.requestDidFailed();
			}
		}
	}

	@Override
	protected String doInBackground(Void... params) {
		isLoading = true;
		return request();
	}

	/**
	 * 网络请求回调接口
	 * 
	 * @author 李航杰
	 */
	public static interface RequestCallback {

		/**
		 * 网络请求成功，返回http响应报文body
		 * 
		 * @param body
		 * @exception throws
		 */
		void requestDidFinished(String body);

		/**
		 * 网络请求失败，如网络超时、响应码非200
		 * 
		 * @exception throws
		 */
		void requestDidFailed();
	}

}
